# Title     : TODO
# Objective : TODO
# Created by: Administrator
# Created on: 2019/7/24

library(ggrepel)
library(ropls)
library(pROC)
library(egg)
library(randomForest)
library(Boruta)
library(magrittr)
library(optparse)
require(gbm)
library(caret)
library(tidyverse)

createWhenNoExist <- function(f) {
  !dir.exists(f) && dir.create(f)
}

option_list <- list(
  make_option("--i", default = "../AllMet_Raw.txt", type = "character", help = "metabolite data file"),
  make_option("--g", default = "../group.txt", type = "character", help = "sample group file"),
  make_option("--sc", default = "sample_color.txt", type = "character", help = "sample color file"),
  make_option("--config", default = "../calculate_config.txt", type = "character", help = "config file")

)
opt <- parse_args(OptionParser(option_list = option_list))

options(digits = 3)

args <- commandArgs(trailingOnly = F)
scriptPath <- dirname(sub("--file=", "", args[grep("--file", args)]))
source(str_c(scriptPath, "/base.R"))

sampleInfo <- read_tsv(opt$g) %>%
  rename(SampleID = Sample) %>%
  select(c("SampleID", "ClassNote"))

groups<-sampleInfo %>%
  .$ClassNote %>%
  unique()

parent <- paste0("./")
createWhenNoExist(parent)

fileName <- opt$i
if (!file.exists(fileName)) {
  quit(status = 0)
}

originalData <- read_tsv(fileName) %>%
  gather("SampleID", "Value", -Metabolite) %>%
  spread(Metabolite, "Value")

originalColumnNames<-colnames(originalData)

data <- originalData %>%
  inner_join(sampleInfo, by = c("SampleID")) %>%
  mutate(ClassNote = factor(ClassNote, levels = unique(ClassNote)))

configJson <- fromJSON(opt$config)
hasExternal <- configJson$hasExternal  %>%
  as.logical()
testSampleInfoTb <- if (hasExternal) {
  read_tsv(str_c("../test_group.txt"))
}else {
  read_tsv(str_c("../../preprocess_0/test_group.txt"))
}
testSampleInfo <- testSampleInfoTb %>%
  rename(SampleID = Sample) %>%
  select(c("SampleID", "ClassNote")) %>%
  filter(ClassNote %in% groups)

trainData <- data %>%
  column_to_rownames("SampleID")

testDataTb <- read_tsv("../test.txt")
testData <- testDataTb %>%
  gather("SampleID", "Value", -Metabolite) %>%
  spread(Metabolite, "Value") %>%
  select(originalColumnNames) %>%
  column_to_rownames("SampleID")

x <- trainData %>% select(-c("ClassNote"))
y <- trainData$ClassNote

ntree <- configJson$ntree %>%
  as.numeric()
hasMtry <- configJson$hasMtry %>%
  as.logical()
mtry <- if (hasMtry) {
  configJson$mtry %>%
    as.numeric()
}else {
  if (!is.null(y) && !is.factor(y))
    max(floor(ncol(x) / 3), 1) else floor(sqrt(ncol(x)))
}
hasNodesize <- configJson$hasNodesize %>%
  as.logical()
nodesize <- if (hasNodesize) {
  configJson$nodesize %>%
    as.numeric()
}else {
  if (!is.null(y) && !is.factor(y)) 5 else 1
}
hasMaxnode <- configJson$hasMaxnode %>%
  as.logical()
maxnodes <- if (hasMaxnode) {
  configJson$maxnodes %>%
    as.numeric()
}else {
  NULL
}
replace <- configJson$replace  %>%
  as.logical()
rfRs <- randomForest(x, y, importance = T, proximity = TRUE, ntree = ntree, mtry = mtry, replace = replace,
                     nodesize = nodesize)

predData <- predict(rfRs, testData)
prob <- predict(rfRs, testData, type = "prob")

print("===")

predDf1 <- prob %>%
  as.data.frame(check.names = F, stringsAsFactors = F) %>%
  rownames_to_column("SampleID") %>%
  rowwise() %>%
  do({
    result <- as.data.frame(.)
    values <- result[1,] %>%
      select(-c("SampleID")) %>%
      unlist()
    result$Value <- values[1]
    result
  }) %>%
  select(c("SampleID", "Value")) %>%
  add_column(Prediction = predData)
predictFinalDf1 <- testSampleInfo %>%
  left_join(predDf1, by = c("SampleID"))
write_tsv(predictFinalDf1, "Classification_Result.txt")

predDf <- prob %>%
  as.data.frame(check.names = F, stringsAsFactors = F) %>%
  rownames_to_column("SampleID") %>%
  rowwise() %>%
  do({
    result <- as.data.frame(.)
    values <- result[1,] %>%
      select(-c("SampleID")) %>%
      unlist()
    result$Probability <- max(values)
    result
  }) %>%
  select(c("SampleID", "Probability")) %>%
  add_column(Prediction = predData)
predictFinalDf <- testSampleInfo %>%
  inner_join(predDf, by = c("SampleID")) %>%
  rename(Sample = SampleID) %>%
  select(-c("Probability"), "Probability")
write_csv(predictFinalDf, "RF_Prediction.csv")

varImp <- rfRs$importance
varImpDf <- varImp %>%
  as.data.frame() %>%
  rownames_to_column("Metabolite") %>%
  as_tibble() %>%
  select(c("Metabolite", "MeanDecreaseAccuracy")) %>%
  rename(VarImp = MeanDecreaseAccuracy) %>%
  arrange(desc(VarImp))
write_csv(varImpDf, "RF_VarImp.csv")

pre_summary = table(predictFinalDf$ClassNote, predictFinalDf$Prediction)

summaryTb <- pre_summary %>%
  as.data.frame() %>%
  as_tibble() %>%
  rename(Var1 = 1, Var2 = 2) %>%
  spread(Var2, "Freq")
summaryMatrix <- summaryTb %>%
  select(-"Var1") %>%
  as.matrix()
diagSum <- sum(diag(summaryMatrix))
sum <- sum(summaryMatrix)
predictive <- (diagSum / sum) %>%
  round(3)
finalSummaryTb <- summaryTb %>%
  mutate(`Model predictive accuracy` = c(predictive, "")) %>%
  rename(` ` = Var1)
finalSummaryTb
write_csv(finalSummaryTb, "RF_Prediction_Summary.csv")










